package com.lcm.weam.controller.pro;

import com.aliyun.oss.OSS;
import com.aliyun.oss.model.OSSObject;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.IdWorker;
import com.lcm.weam.entity.pro.Member;
import com.lcm.weam.entity.pro.Project;
import com.lcm.weam.entity.req.ProjectMap;
import com.lcm.weam.entity.resp.PageResult;
import com.lcm.weam.entity.resp.ProfileResult;
import com.lcm.weam.entity.resp.Result;
import com.lcm.weam.entity.resp.ResultCode;
import com.lcm.weam.entity.sys.FileList;
import com.lcm.weam.service.pro.MemberService;
import com.lcm.weam.service.pro.ProjectService;
import com.lcm.weam.util.AliOSSUtil;
import org.apache.commons.lang3.StringUtils;
import org.apache.shiro.SecurityUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.InputStream;
import java.net.URLEncoder;
import java.nio.charset.StandardCharsets;
import java.util.Date;
import java.util.List;

/**
 * 项目接口
 * 1、新建项目
 * 2、id编辑项目信息
 * 3、id删除项目
 * 4、地图首页查询所有公开项目、个人私有项目
 * 5、根据uid查询所有项目（分页）
 * 6、根据uid查询指定条件项目（分页）
 * 7、点击进入该项目，发送一次请求返回单个project
 * 8、记录今日访问、累计访问
 * 9、上传项目文件到阿里云（项目文件模块）
 * 10、列举项目文件（项目文件模块）
 * 11、下载项目文件（项目文件模块）
 * 12、删除项目文件（项目文件模块）
 */
@CrossOrigin
@RestController
@RequestMapping(value = "/pro")
public class ProjectController {

    @Autowired
    private ProjectService projectService;

    @Autowired
    private MemberService memberService;

    /**
     * 1、新建项目
     */
    @RequestMapping(value = "/createPro", method = RequestMethod.POST)
    public Result createPro(@RequestBody Project project) {
        ProfileResult o = (ProfileResult) SecurityUtils.getSubject().getPrincipal(); //获取当前登录用户
        project.setProid(IdWorker.getIdStr()); //雪花算法设置
        project.setCreater(o.getUsername()); //设置用户名称
        project.setUid(o.getUid()); //设置用户id
        project.setCreateTime(new Date()); //设置创建时间
        String proid = projectService.createPro(project); //创建项目
        Member member = new Member(proid, o.getUsername(), new Date(), "默认创建人为项目负责人", "项目负责人");
        memberService.createMember(member); //默认将创建人列入负责人
        return new Result(ResultCode.SUCCESS);
    }

    /**
     * 2、编辑项目信息 (权限管理)
     */
    @RequestMapping(value = "/editPro", method = RequestMethod.PUT)
    public Result editPro(@RequestBody Project project) {
        //确认当前登录用户是所选项目的创建者
        boolean bool = projectService.checkUser(project.getProid());
        if (bool){
            projectService.editPro(project); //传入的project有proid
            return new Result(ResultCode.SUCCESS);
        }
        return new Result(ResultCode.UNAUTHORISE);
    }

    /**
     * 3、删除项目 (权限管理)
     */
    @RequestMapping(value = "/deletePro", method = RequestMethod.DELETE)
    public Result deletePro(String proid) {
        //确认当前登录用户是所选项目的创建者
        boolean bool = projectService.checkUser(proid);
        if (bool){
            projectService.deletePro(proid);
            return new Result(ResultCode.SUCCESS);
        }
        return new Result(ResultCode.UNAUTHORISE);
    }

    /**
     * 4、地图首页查询所有公开项目、个人私有项目
     */
    @RequestMapping(value = "/selectAllPro", method = RequestMethod.GET)
    public Result selectAllPro() {
        ProfileResult o = (ProfileResult)SecurityUtils.getSubject().getPrincipal();
        List<Project> list = projectService.selectAllPro(o.getUid());
        return new Result(ResultCode.SUCCESS, list);
    }

    /**
     * 5、根据uid查询所有项目（分页）
     */
    @RequestMapping(value = "/{uid}/selectUserPro", method = RequestMethod.GET)
    public Result selectUserPro(@PathVariable String uid, int pageIndex, int pageSize) {
        IPage<Project> page = projectService.selectUserPro(uid,pageIndex,pageSize);
        PageResult<Project> pageResult = new PageResult<>((int)page.getTotal(), (int)page.getPages() ,page.getRecords());
        return new Result(ResultCode.SUCCESS, pageResult);
    }

    /**
     * 6、根据uid查询指定条件项目（分页）
     *      type、status、description(like)、pro_name(like)
     */
    @RequestMapping(value = "/{uid}/selectUserProTS", method = RequestMethod.GET)
    public Result selectUserProTS(@PathVariable String uid, int pageIndex, int pageSize, @RequestBody ProjectMap projectMap) {
        IPage<Project> page = projectService.selectUserProTS(uid,pageIndex,pageSize,projectMap);
        PageResult<Project> pageResult = new PageResult<>((int)page.getTotal(), (int)page.getPages() ,page.getRecords());
        return new Result(ResultCode.SUCCESS, pageResult);
    }

    /**
     * 7、点击进入该项目，发送一次请求返回单个project
     */
    @RequestMapping(value = "/{proid}", method = RequestMethod.GET)
    public Result intoAPro(@PathVariable String proid) {
        Project project = projectService.intoAPro(proid);
        return new Result(ResultCode.SUCCESS, project);
    }

    /**
     * 8、记录今日访问、累计访问
     */


    /**
     * 9、上传项目文件到阿里云（项目文件模块）
     */
    @RequestMapping(value = "/{proid}/uploadFileAliOSS", method = RequestMethod.POST)
    public Result uploadFileAliOSS(MultipartFile file, String filename, @PathVariable String proid) throws IOException {
        projectService.uploadFileAliOSS(proid, file, filename);
        return new Result(ResultCode.SUCCESS);
    }

    /**
     * 10、列举项目文件（项目文件模块）
     */
    @RequestMapping(value = "/{proid}/listFiles", method = RequestMethod.GET)
    public Result listFiles(int page, int num, @PathVariable String proid) {
        if (page > 0 && num > 0) {
            PageResult<FileList> pageResult = projectService.listFiles(proid, page, num);
            return new Result(ResultCode.SUCCESS, pageResult);
        } else {
            return new Result(ResultCode.FAIL);
        }
    }

    /**
     * 11、下载项目文件（项目文件模块）
     */
    @RequestMapping(value = "{proid}/download", method = RequestMethod.GET)
    public Result download(@PathVariable String proid, String objectName, HttpServletRequest request, HttpServletResponse response) throws IOException {
        AliOSSUtil aliOSSUtil = new AliOSSUtil();
        OSS download = aliOSSUtil.download(); //记得关闭
        OSSObject object = download.getObject("weam", "projectFile/" + proid + "/" + objectName);
        final String userAgent = request.getHeader("USER-AGENT");
        String finalFileName = null;
        if (StringUtils.contains(userAgent, "MSIE") || StringUtils.contains(userAgent, "Trident")) {
            finalFileName = URLEncoder.encode(objectName, StandardCharsets.UTF_8);
            System.out.println("适配IE浏览器编码");
        } else if (StringUtils.contains(userAgent, "Mozilla")) {
            finalFileName = URLEncoder.encode(objectName, "ISO8859-1");
            System.out.println("适配谷歌、火狐浏览器编码");
        } else {
            finalFileName = URLEncoder.encode(objectName, StandardCharsets.UTF_8);
            System.out.println("适配其他浏览器的编码格式");
        }
        response.reset();
        response.setContentType("application/octet-stream");
        response.addHeader("Content-Disposition", "attachment;filename=\"" + finalFileName + "\"");

        InputStream istream = object.getObjectContent();
        ServletOutputStream ostream = response.getOutputStream();
        byte[] bytes = new byte[1024];
        int len;
        while ((len = istream.read(bytes)) > 0) {
            ostream.write(bytes, 0, len);
        }
        istream.close();
        ostream.close();
        download.shutdown(); //关闭
        return new Result(ResultCode.SUCCESS);
    }

    /**
     * 12、删除项目文件（项目文件模块）
     */
    @RequestMapping(value = "{proid}/delete", method = RequestMethod.DELETE)
    public Result delete(String fileName, @PathVariable String proid) {
        AliOSSUtil aliOSSUtil = new AliOSSUtil();
        String res = aliOSSUtil.detete("projectFile/" + proid + "/" + fileName);
        return new Result(ResultCode.SUCCESS, res);
    }
}
